home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 5 / Apprentice-Release5.iso / Source Code / C++ / Frameworks / Sprocket Framework DR2 / Sprocket Framework / File.cp < prev    next >
Text File  |  1996-06-15  |  8KB  |  383 lines

  1. /*
  2.  
  3.     File:        File.cp
  4.     Project:    Sprocket Framework 1.1 (DR2), released 6/15/96
  5.     Contains:    File handling routines
  6.     To Do:        Add support for management of files through aliases
  7.  
  8.     Sprocket Major Contributors:
  9.     ----------------------------
  10.     Dave Falkenburg, producer of Sprocket 1.0
  11.     Bill Hayden,     producer of Sprocket 1.1
  12.     Steve Sisak,     producer of the upcoming Sprocket 2.0
  13.     
  14.     Pete Alexander        Steve Falkenburg    Randy Thelen
  15.     Eric Berdahl        Nitin Ganatra        Chris K. Thomas
  16.     Marshall Clow        Dave Hershey        Leonard Rosenthal
  17.     Tim Craycroft        Dave Mark            Dean Yu
  18.     David denBoer        Gary Powell
  19.     Cameron Esfahani    Jon Summers            Apple Computer, Inc.
  20.         
  21.     Comments, Additions, or Corrections:
  22.     ------------------------------------
  23.     Bill Hayden, Nikol Software <nikol@codewell.com>
  24.  
  25. */
  26.  
  27. #include "File.h"
  28. #include "UResources.h"
  29.  
  30.  
  31. const short        kUndefinedRefNum    = -1;
  32.  
  33.  
  34.  
  35. /*****************************************************************************/
  36.  
  37.  
  38.  
  39. TFile::TFile()
  40. {
  41.     fFileSpec.vRefNum = 0;
  42.     fFileSpec.parID = 0;
  43.     fFileSpec.name[0] = 0;
  44.     fDataForkRefNum = kUndefinedRefNum;
  45.     fResourceForkRefNum = kUndefinedRefNum;
  46. }
  47.  
  48.  
  49.  
  50. /*****************************************************************************/
  51.  
  52.  
  53. //    Contruct a File from a Toolbox File System Specification
  54.  
  55. TFile::TFile(const FSSpec &inFileSpec)
  56. {
  57.     fFileSpec = inFileSpec;
  58.     fDataForkRefNum = kUndefinedRefNum;
  59.     fResourceForkRefNum = kUndefinedRefNum;
  60. }
  61.  
  62.  
  63.  
  64.  
  65. /*****************************************************************************/
  66.  
  67.  
  68.  
  69. //    Contruct a File from an Alias
  70. //
  71. //    outWasChanged indicates if the AliasHandle was changed during resolution
  72. //    inFromFile is a File Specifier for the starting point for a relative
  73. //    search. If nil, an absolute search is performed
  74.  
  75. TFile::TFile(AliasHandle inAlias, Boolean &outWasChanged, FSSpec *inFromFile)
  76. {
  77.     OSErr    err = ::ResolveAlias(inFromFile, inAlias, &fFileSpec, &outWasChanged);
  78.     fDataForkRefNum = kUndefinedRefNum;
  79.     fResourceForkRefNum = kUndefinedRefNum;
  80.     
  81.     if (err)
  82.         delete this;
  83. }
  84.  
  85.  
  86.  
  87. /*****************************************************************************/
  88.  
  89.  
  90.  
  91. TFile::~TFile()
  92. {
  93.     CloseDataFork();
  94.     CloseResourceFork();
  95. }
  96.  
  97.  
  98.  
  99. /*****************************************************************************/
  100.  
  101.  
  102.  
  103. //    Return the Toolbox File System Specification for a File
  104.  
  105. void TFile::GetSpecifier(FSSpec    &outFileSpec) const
  106. {
  107.     outFileSpec = fFileSpec;
  108. }
  109.  
  110.  
  111.  
  112. /*****************************************************************************/
  113.  
  114.  
  115.  
  116. //    Set a new Toolbox File System Specification for a File
  117. //    This also closes any open forks of the file identified by the old Specifier
  118.  
  119. void TFile::SetSpecifier(FSSpec    &inFileSpec)
  120. {
  121.     CloseDataFork();
  122.     CloseResourceFork();
  123.     
  124.     fFileSpec = inFileSpec;
  125. }
  126.  
  127.  
  128.  
  129. /*****************************************************************************/
  130.  
  131.  
  132. //    Return a newly created Alias for a File
  133. //
  134. //    inFromFile is a File Specifier for the starting point for a relative
  135. //        search. Pass nil if you don't need relative path information.
  136.  
  137. AliasHandle TFile::MakeAlias(FSSpec    *inFromFile)
  138. {
  139.     AliasHandle    theAlias;
  140.     OSErr    err = ::NewAlias(inFromFile, &fFileSpec, &theAlias);
  141.     
  142.     return theAlias;
  143. }
  144.  
  145.  
  146.  
  147. /*****************************************************************************/
  148.  
  149.  
  150.  
  151. //    Create a new disk File, with an empty data fork and a resoure map.
  152. //    You must call OpenDataFork or OpenResourceFork (with write permission)
  153. //    before you can store information in the File.
  154. //
  155. //    If the file already exists, but doesn't have a resource map, this
  156. //    function will create a resource map.
  157.  
  158. OSErr TFile::CreateNewFile(OSType inCreator, OSType inFileType, ScriptCode inScriptCode)
  159. {
  160.     ::FSpCreateResFile(&fFileSpec, inCreator, inFileType, inScriptCode);
  161.     return (ResError());
  162. }
  163.  
  164.  
  165.  
  166. /*****************************************************************************/
  167.  
  168.  
  169.  
  170. //    Create a new disk File, with an empty data fork and no resource map.
  171. //    You must call OpenDataFork (with write permission) before you can store
  172. //    data in the File.
  173. //
  174. //    The resource fork is uninitialized (no resource map), so you can't call
  175. //    OpenResourceFork for the File. You can initialize the resource fork
  176. //    by calling CreateNewFile.
  177.  
  178. OSErr TFile::CreateNewDataFile(OSType inCreator, OSType inFileType, ScriptCode inScriptCode)
  179. {
  180.     return ::FSpCreate(&fFileSpec, inCreator, inFileType, inScriptCode);
  181. }
  182.  
  183.  
  184.  
  185.  
  186. /*****************************************************************************/
  187.  
  188.  
  189.  
  190. //    Open the data fork of a File with the specified permissions and
  191. //    return the reference number for the opened fork
  192. //
  193. //    A data fork must be Open before you can read or write data
  194.  
  195. short TFile::OpenDataFork(short inPrivileges)
  196. {
  197.     OSErr    err = ::FSpOpenDF(&fFileSpec, inPrivileges, &fDataForkRefNum);
  198.     if (err != noErr)
  199.         {
  200.         fDataForkRefNum = kUndefinedRefNum;
  201.         }
  202.         
  203.     return fDataForkRefNum;
  204. }
  205.  
  206.  
  207.  
  208. /*****************************************************************************/
  209.  
  210.  
  211.  
  212. //    Close the data fork of a File
  213.  
  214. OSErr TFile::CloseDataFork()
  215. {
  216.     if (fDataForkRefNum != kUndefinedRefNum)
  217.         {
  218.         OSErr    err = ::FSClose(fDataForkRefNum);
  219.         fDataForkRefNum = kUndefinedRefNum;
  220.         
  221.         ::FlushVol(nil, fFileSpec.vRefNum);
  222.         
  223.         return err;
  224.         }
  225.         
  226.     return fnfErr;
  227. }
  228.  
  229.  
  230.  
  231.  
  232. /*****************************************************************************/
  233.  
  234.  
  235.  
  236. //    Return the file reference number for a File's data fork
  237. //
  238. //    You can use this number in calls to Toolbox File Manager routines.
  239. //    The only restriction is don't call FSClose. Use the member function
  240. //    CloseDataFork instead.
  241.  
  242. short TFile::GetDataForkRefNum() const
  243. {
  244.     return fDataForkRefNum;
  245. }
  246.  
  247.  
  248.  
  249. /*****************************************************************************/
  250.  
  251.  
  252.  
  253. //    Read the entire contents of a File's data fork into a newly created
  254. //    Handle. The caller is responsible for disposing of the Handle.
  255.  
  256. Handle TFile::ReadDataFork()
  257. {
  258.     Handle    dataHandle = nil;
  259.     
  260.     long    fileLength;
  261.     OSErr    err = ::GetEOF(fDataForkRefNum, &fileLength);
  262.     if (err)
  263.         return nil;
  264.     
  265.     dataHandle = ::NewHandle(fileLength);
  266.     if (MemError() || !dataHandle)
  267.         return nil;
  268.     
  269.     err = ::SetFPos(fDataForkRefNum, fsFromStart, 0);
  270.     if (err)
  271.         {
  272.         DisposeHandle(dataHandle);
  273.         return nil;
  274.         }
  275.     
  276.     err = ::FSRead(fDataForkRefNum, &fileLength, *dataHandle);
  277.     if (err)
  278.         {
  279.         DisposeHandle(dataHandle);
  280.         return nil;
  281.         }
  282.     
  283.     return dataHandle;
  284. }
  285.  
  286.  
  287.  
  288.  
  289. /*****************************************************************************/
  290.  
  291.  
  292.  
  293. //    Write to the data fork of a File from a buffer
  294. //
  295. //    The buffer contents completely replace any existing data
  296.  
  297. long    TFile::WriteDataFork(const void    *inBuffer, long inByteCount)
  298. {
  299.     long    bytesWritten = inByteCount;
  300.     
  301.     OSErr    err = ::SetFPos(fDataForkRefNum, fsFromStart, 0);
  302.     if (err)
  303.         return 0;
  304.     
  305.     err = ::FSWrite(fDataForkRefNum, &bytesWritten, inBuffer);
  306.     ::SetEOF(fDataForkRefNum, bytesWritten);
  307.  
  308.     return bytesWritten;
  309. }
  310.  
  311.  
  312.  
  313. /*****************************************************************************/
  314.  
  315.  
  316.  
  317. //    Open the resource fork of a File with the specified permissions and
  318. //    return the reference number for the opened fork
  319. //
  320. //    A resource fork must be Open before you can read or write resources
  321.  
  322. short    TFile::OpenResourceFork(short inPrivileges)
  323. {
  324.     return ::FSpOpenResFile(&fFileSpec, inPrivileges);
  325. }
  326.  
  327.  
  328.  
  329.  
  330. /*****************************************************************************/
  331.  
  332.  
  333.  
  334. OSStatus    TFile::CloseResourceFork()
  335. {
  336.     OSStatus err = noErr;
  337.     
  338.     
  339.     if (fResourceForkRefNum != kUndefinedRefNum)
  340.         {
  341.         err = RMCloseResFileCompat(fResourceForkRefNum);
  342.         fResourceForkRefNum = kUndefinedRefNum;
  343.         ::FlushVol(nil, fFileSpec.vRefNum);
  344.         }
  345.         
  346.     return err;
  347. }
  348.  
  349.  
  350.  
  351. /*****************************************************************************/
  352.  
  353.  
  354.  
  355. //    Return the file reference number for a File's resource fork
  356. //
  357. //    You can use this number in calls to Toolbox Resource Manager routines.
  358. //    The only restriction is don't call CloseResFile. Use the member function
  359. //    CloseResourceFork instead.
  360.  
  361. short    TFile::GetResourceForkRefNum() const
  362. {
  363.     return fResourceForkRefNum;
  364. }
  365.  
  366.  
  367.  
  368.  
  369. /*****************************************************************************/
  370.  
  371.  
  372.  
  373. //    Delete the file
  374. //
  375. //    Use this function to delete the physical file specified by the class
  376.  
  377. OSErr    TFile::Delete(void)
  378. {
  379.     CloseDataFork();
  380.     CloseResourceFork();
  381.  
  382.     return ::FSpDelete( &fFileSpec );
  383. }